package com.ikun.admin.modules.gen.iservice.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.ikun.admin.modules.gen.entity.FieldType;
import com.ikun.admin.modules.gen.entity.Table;
import com.ikun.admin.modules.gen.entity.TableEntity;
import com.ikun.admin.modules.gen.iservice.ITableService;
import com.ikun.admin.modules.gen.service.CodeConfigService;
import com.ikun.admin.modules.gen.service.FieldTypeService;
import com.ikun.admin.modules.gen.service.TableEntityService;
import com.ikun.admin.modules.gen.service.TableService;
import com.ikun.admin.modules.gen.vo.*;
import com.ikun.common.exception.MyException;
import com.ikun.common.result.Result;
import com.ikun.common.search.PageData;
import com.ikun.common.search.PageResult;
import com.ikun.common.search.build.QueryBuilder;
import com.ikun.common.search.build.ResultBuilder;
import com.ikun.common.utils.DataCopy;
import com.ikun.common.validate.validator.Validate;
import com.ikun.common.validate.validator.ValidateExecutor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.Objects;

/**
 * @ClassName ITableServiceImpl
 * @Description:
 * @CreateDate: 2024/4/16 15:01
 */
@Service
public class ITableServiceImpl implements ITableService {

    @Autowired
    private TableService tableService;
    @Autowired
    private TableEntityService tableEntityService;
    @Autowired
    private CodeConfigService codeConfigService;

    @Autowired
    private FieldTypeService fieldTypeService;

    private void checkField(TableEntity tableEntity) {

        if(Objects.isNull(tableEntity.getFieldName())){
            throw new MyException("请填写字段逻辑名");
        }
        if (Objects.isNull(tableEntity.getFieldValue())) {
            throw new MyException("请选择字段类型");
        }
        FieldType fieldType = fieldTypeService.getOne(new QueryWrapper<FieldType>().lambda().eq(FieldType::getFieldValue, tableEntity.getFieldValue()));
        if (fieldType.getTypeLength() == 0 && Objects.isNull(tableEntity.getTypeLength())) {
            throw new MyException("字段:" + tableEntity.getFieldName() + "的字段类型长度需要指定");
        }
        if (fieldType.getTypeHold() == 0 && Objects.isNull(tableEntity.getReservedBit())) {
            throw new MyException("字段:" + tableEntity.getFieldName() + "的字段类型保留小数位数需要指定");
        }
    }

    @Override
    @Transactional
    public Result<String> tableAddOrUpdate(TableAddOrUpdateVo tableAddOrUpdateVo) {
        ValidateExecutor.execute(tableAddOrUpdateVo, null);
//        SELECT  查询是否存在指定表名
//    COUNT(*)
//FROM
//    information_schema.tables
//WHERE
//    table_schema = 'your_database_name' AND
//    table_name = 'your_table_name';
        if (Objects.isNull(tableAddOrUpdateVo.getId())) {
            Table table = DataCopy.copyToObj(tableAddOrUpdateVo, Table.class);
            tableService.save(table);
        } else {
            tableService.update(new UpdateWrapper<Table>().lambda().eq(Table::getId, tableAddOrUpdateVo.getId())
                    .set(Table::getTableName, tableAddOrUpdateVo.getTableName())
                    .set(Table::getTableValue, tableAddOrUpdateVo.getTableValue())
                    .set(Table::getCodeConfigId, tableAddOrUpdateVo.getCodeConfigId()));
        }
        return new Result<String>().success("操作成功");
    }

    @Override
    public Result<PageResult<TableListResultVo>> tableList(PageData<TableListParamVo> pageData) {
        QueryWrapper<Table> tableQueryWrapper = new QueryWrapper<>();
        Boolean queryBuild = QueryBuilder.build(tableQueryWrapper, pageData.getCondition());
        if (!queryBuild) {
            return new Result<PageResult<TableListResultVo>>().success(new PageResult<>(0l, null));
        }

        IPage<Table> page = new Page<>();

        tableService.page(page, tableQueryWrapper);

        List<TableListResultVo> resultVoList = new ArrayList<>();
        if (page.getRecords().size() > 0) {
            ResultBuilder.buildResult(page.getRecords(), resultVoList, TableListResultVo.class);
        }
        return new Result<PageResult<TableListResultVo>>().success(new PageResult<>(page.getTotal(), resultVoList));
    }

    @Override
    @Transactional
    public Result<String> tableDelete(Long id) {
        tableService.removeById(id);
        tableEntityService.remove(new QueryWrapper<TableEntity>()
                .lambda()
                .eq(TableEntity::getTableId, id));
        return new Result<String>().success("操作成功");
    }

    @Override
    public Result<List<TableListResultVo>> tableDict() {
        List<Table> tableList = tableService.list(new QueryWrapper<>());
        List<TableListResultVo> resultList = DataCopy.copyToListObj(tableList, TableListResultVo.class);
        return new Result<List<TableListResultVo>>().success(resultList);
    }

    @Override
    public Result<TableDetailVo> tableDetail(Long id) {
        Table table = tableService.getById(id);
        TableDetailVo tableDetailVo = DataCopy.copyToObj(table, TableDetailVo.class);

        return new Result<TableDetailVo>().success(tableDetailVo);
    }

    @Override
    public Result<List<TableFieldDetailVo>> tableFieldDetail(Long id) {

        List<TableEntity> tableEntityList = tableEntityService.list(new QueryWrapper<TableEntity>().lambda().eq(TableEntity::getTableId, id));

        List<TableFieldDetailVo> tableFieldDetailVoList = DataCopy.copyToListObj(tableEntityList, TableFieldDetailVo.class);
        return new Result<List<TableFieldDetailVo>>().success(tableFieldDetailVoList);
    }

    @Override
    @Transactional
    public Result<String> tableEntityAddOrUpdate(TableEntityAddOrUpdateVo tableEntityAddOrUpdateVo) {
        ValidateExecutor.execute(tableEntityAddOrUpdateVo,null);
        List<TableEntity> tableEntityList = DataCopy.copyToListObj(tableEntityAddOrUpdateVo.getTableFieldDetailVoList(), TableEntity.class);
        tableEntityList.stream().forEach(item->this.checkField(item));
        if (Objects.isNull(tableEntityAddOrUpdateVo.getId())) {
            tableEntityList.stream().forEach(item -> item.setTableId(tableEntityAddOrUpdateVo.getTableId()));
        } else {
            tableEntityService.remove(new QueryWrapper<TableEntity>().lambda().eq(TableEntity::getTableId,tableEntityAddOrUpdateVo.getTableId()));
        }
        tableEntityService.saveBatch(tableEntityList);
        return new Result<String>().success("操作成功");
    }
}
